/* -----------------------------------------------------------------------
 * Demonstration of how to write unit tests for dominion-base
 * Include the following lines in your makefile:
 *
 * unittest2: unittest2.c dominion.o rngs.o
 *      gcc -o testUpdateCoins -g  unittest2.c dominion.o rngs.o $(CFLAGS)
 * -----------------------------------------------------------------------
 */

#include "dominion.h"
#include "dominion_helpers.h"
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <assert.h>
#include <time.h>
#include "rngs.h"
int main() {
	//testing villageCard
	int x;
	int y;
	int z;
	struct gameState G;
	struct gameState copyG;
	int numberOfCardsPassed = 0;
	int treasureCount= 0;
	int coinIncrease = 0;
	int numPlayer = 2;
	int seed = 2;
	int k[10] = {adventurer, council_room, feast, gardens, mine
		, remodel, smithy, village, baron, great_hall};
	int allCards[17]={adventurer, council_room, feast, gardens, mine
		, remodel, smithy, village, baron, great_hall, copper, silver, gold, curse, estate, duchy, province};
	int playCardSuccess = 0;
	
	
	//want to randomize:
	//  Number of cards in hand (why not?)
	//  Number of cards in deck (important!)
	//  Number of cards in discard
	//  Position of card in hand (again, why not?)
	//  Which cards are in hand
	//  Which cards are in deck
	//  Which cards are in discard
	
	
	printf("Testing Adventurer Card\n");
	
	srand(time(NULL));//seed the rand function to time
	
	//want to randomize:
	//  Presense/absense of each treasure card
	//  position of card in hand
	//  number of cards in hand
	//  number of actions available
	//  number of cards in draw pile
	//  number of cards in discard pile
	//  different players as well
	
	//Need to test after playing card:
	//  Number of cards in deck
	//  Number of cards in discard
	//  Number of cards in hand
	//  Value of cards in hand
	
	//initialize to standardish value, then change for random fxn
	int handCount=5;
	int handPos=0;
	int actionCount=1;
	int drawPileCount=5;
	int discardCount=5;
	int player = 0;
	
	
	
	
	
	for (x = 0; x<5000000; x++) {
		initializeGame(numPlayer, k, seed, &G); // initialize a new game,
		
		coinIncrease = 0;
		treasureCount=0;
		numberOfCardsPassed = 0;
		//randomize above changes
		
		//the MAX_HAND count is 500. not likely. So only one in 50 times will we test that high.
		//the rest will be reasonbly up to 50
		if (x%50 ==0) {
			handCount = (rand() % MAX_HAND)+1;//we want anywhere from 1 to MAX_HAND
			drawPileCount = (rand() % MAX_DECK); //from zero to max deck
			discardCount = (rand() % (MAX_DECK-drawPileCount)); //from zero to what would make up max deck with the draw pile count
			
		}
		else{
			handCount = (rand() % 10)+1;//we want anywhere from 1 to 5
			drawPileCount = (rand() % 50); //from zero to 10
			discardCount = (rand() % 50); //just a reasonable number
		}
		
		
		
		handPos =   (rand() % handCount); // anywhere from 0 to the handCount
		actionCount = (rand() % 5); //want to go from zero up to 5. I think that's enough
		
		
		player = (rand() % 1); //player 1 or two
		
		//apply the above changes
		G.handCount[player]= handCount;
		//handPos will be used to add the card to the hand
		G.numActions = actionCount;
		G.deckCount[player] = drawPileCount;
		G.discardCount[player] = discardCount;
		
		//set which cards are in deck
		for (y = 0; y<drawPileCount; y++) {
			z = rand() % 17;//17 is the number of different cards
			G.deck[player][y]=allCards[z];
		}
		
		//set which cards are in hand
		for (y = 0; y<handCount; y++) {
			z = rand() % 17;//17 is the number of different cards
			G.deck[player][y]=allCards[z];
		}	
		
		//set which cards are in discard
		for (y = 0; y<discardCount; y++) {
			z = rand() % 17;//17 is the number of different cards
			G.deck[player][y]=allCards[z];
		}
		
		
		//put the adventurer card into the hand at the handPos position
		G.hand[player][handPos]= adventurer;
		
		
		memcpy(&copyG,&G, sizeof(G));//copy everything to a separate hand for comparisons
		
		//make sure there are available treasure cards
		for (y=drawPileCount-1; y>=0; y--) {
			if (G.deck[player][y] == copper) {
				treasureCount +=1;
				coinIncrease +=1;
			}
			else if (G.deck[player][y] == silver) {
				treasureCount +=1;
				coinIncrease +=2;
			}
			else if (G.deck[player][y] == gold) {
				treasureCount +=1;
				coinIncrease +=3;
			}
			else {//not a treasure card, passing it. (will go to discard later)
				numberOfCardsPassed += 1;
			}
			
			//once we have two treasure cards we are good
			if(treasureCount ==2){
				break;
			}
		}
		
		//if there were not enough treasure cards in deck, we have to check discard
		if (treasureCount < 2) {
			for (y=discardCount-1; y<=0; y--) {
				if (G.discard[player][y] == copper) {
					treasureCount +=1;
					coinIncrease +=1;
				}
				else if (G.discard[player][y] == silver) {
					treasureCount +=1;
					coinIncrease +=2;
				}
				else if (G.discard[player][y] == gold) {
					treasureCount +=1;
					coinIncrease +=3;
				}
				else {//not a treasure card, passing it.
					//we need to shuffle, so we don't need to keep track of this
				}
				//once we have two treasure cards we are good
				if(treasureCount ==2){
					break;
				}
			}
		}
		
		
		//		printf("The coin increase will be: %d\n", coinIncrease);
		//		
		/////////////////////////////////////////////////////////////////
		//force area
		//		memset(&G, 23, sizeof(struct gameState));   // clear the game state (clear code from group member Darren)
		//		initializeGame(numPlayer, k, seed, &G); // initialize a new game,
		//		treasureCount = 2;
		//		coinIncrease = 2;
		//		G.hand[player][handPos]= adventurer;
		//force area fails. seems random assignment of 1 or 2 coin cards
		/////////////////////////////////////////////////////////////////
		
		
		//play the card
		//printf("Before G discard: %d\n", G.discardCount[player]);
		playCardSuccess = playCard(handPos,0,0,0,&G);//the zeros are choices for different cards than village.
		//printf("After G discard: %d\n", G.discardCount[player]);

		
		
		
		//if there are no actions, playCard returns - 1. make sure that works
		if ( (actionCount ==0) && (playCardSuccess== -1) ) {
			//printf("Passed basic card test (no actions)\n");
			continue;
			
		}
	
		
		//all we needed was in the deck (no shuffling)
		if ((numberOfCardsPassed + treasureCount) < copyG.deckCount[player] ) {
			if (
					/*(G.coins == (copyG.coins + coinIncrease))&&*/
					(G.handCount[player] == (copyG.handCount[player]+treasureCount))&&
					(G.discardCount[player] ==(copyG.discardCount[player] + numberOfCardsPassed))
					//NOTE! THIS IS THE ONLY CARD THAT DOES NOT DISCARD DURING PLAY!!! WHY???
					) 
			{
				//printf("Success!\n");
			}
			else {
				printf("Failed basic card test\n");
				//				
				printf("hand count = %d vs expected %d\n", G.handCount[player],handCount + 2);
				//				
				//				printf("Original coin count was: %d \n", copyG.coins);
				//				printf("Extra coin count was: %d\n", coinIncrease);
				printf("Final coin count was: %d vs expected:  %d\n", G.coins, (copyG.coins + coinIncrease));
				//				
				printf("discard count = %d vs expected: %d\n", G.discardCount[player],(copyG.discardCount[player] +numberOfCardsPassed + 1));
				//				printf("draw count = %d\n", drawPileCount);
				//				printf("player number = %d\n", player);
				
			}
		}	
		
		//we had to shuffle
//		else {
//			//printf("We had to shuffle! \n");
//
//				if (
//						/*(G.coins == (copyG.coins + coinIncrease))&&*/
//						(G.handCount[player] == (copyG.handCount[player]+treasureCount))&&
//						((G.discardCount[player] + G.deckCount[player]) == (copyG.discardCount[player] + copyG.deckCount[player]) - treasureCount)
//						//NOTE! THIS IS THE ONLY CARD THAT DOES NOT DISCARD DURING PLAY!!! WHY???
//						) 
//				{
//					if (treasureCount==0) {
//						//printf("Success At Shuffling with no treasure!!\n");
//
//					}
//					//printf("Success At Shuffling!\n");
//				}
//				else {
//					//printf("treasure count = %d \n", treasureCount);
//					//printf("numberOfCardsPassed = %d \n", numberOfCardsPassed);
//					if (treasureCount == 2) {
//						printf("Expected total cards: %d \n",(copyG.discardCount[player] + copyG.deckCount[player]) - treasureCount );
//						printf("Actual total cards: %d \n",(G.discardCount[player] + G.deckCount[player]));
//						
//					}
//
//					//				
//					//printf("hand count = %d vs expected %d\n", G.handCount[player],handCount + 2);
//					//				
//					//				printf("Original coin count was: %d \n", copyG.coins);
//					//				printf("Extra coin count was: %d\n", coinIncrease);
//					//printf("Final coin count was: %d vs expected:  %d\n", G.coins, (copyG.coins + coinIncrease));
//					//				
//					//printf("discard count = %d vs expected: %d\n", G.discardCount[player],numberOfCardsPassed);
//					//				printf("draw count = %d\n", drawPileCount);
//					//				printf("player number = %d\n", player);
//					
//				}
//			}	
		
		
		
	}
	
	
	
	
	
	printf("If there is nothing above this line, then all tests have passed. \n");
	
	
	return 0;
}
